{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Creating pandapipes Networks"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "outputs": [],
   "source": [
    "This tutorial will introduce the user into the pandapipes datastructure and how to create networks through the pandapipes API. The following minimal example contains the most common elements that are supported by the pandapipes format. \n",
    "\n",
    "<img src=\"pics/simple_network-1.png\">\n",
    "\n",
    "The datastructure of the pandapipes framework is based on the Python library pandas. A pandapipes network consist of separate tables for each component type that is used in the network and each table holds the elements of its component type. Each row is indexed and represents a single element. The parameters are organized in columns.\n",
    "\n",
    "By executing the follwing code cells you generate the different component tables. You can find detailed descriptions about each parameter in the pandapipes documentation under bulletpoint \"Datastructure and Components\"."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Empty Network"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "First, we import pandapipes and create an empty network:\n",
    "We have to state the name of the fluid for the network. In pandapipes, some fluids are already\n",
    "pre-defined, e.g. <span style=\"color:green\">hgas</span>, <span style=\"color:green\">lgas</span>\n",
    "(high and low calorific natural gas),  <span style=\"color:green\">hydrogen</span>,\n",
    "<span style=\"color:green\">water</span>, <span style=\"color:green\">biomethane_pure</span>, <span style=\"color:green\">biomethane_treated</span> (see [here](https://pandapipes.readthedocs.io/en/latest/fluid_properties/fluids.html) for the composition) and <span style=\"color:green\">air</span>. It is\n",
    "also possible to create a fluid if needed (tutorial in preparation).\n",
    "\n",
    "In this example, we will create a medium pressure gas network and choose <span style=\"color:green\">lgas</span> from the predefined fluids in pandapipes."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "scrolled": true
   },
   "outputs": [],
   "source": [
    "import pandapipes as pp"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net = pp.create_empty_network(fluid=\"lgas\") # create an empty network"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "This network does not hold any elements yet. It serves as a container for the component tables and network specific parameters."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We will now use the <span style=\"color:blue\">create</span> functions to create elements. They will be automatically added to the respective tables. "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Junctions"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<img src=\"pics/simple_network-junc.png\">\n",
    "\n",
    "We now create 6 junctions with an intital pressure for the pipeflow calculation of 1.0 bar. For improved readability, we add names (optional)."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "junction1 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Connection to External Grid\")\n",
    "junction2 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Junction 2\")\n",
    "junction3 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Junction 3\")\n",
    "junction4 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Junction 4\")\n",
    "junction5 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Junction 5\")\n",
    "junction6 = pp.create_junction(net, pn_bar=1.0, tfluid_k=293.15, name=\"Junction 6\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The junctions are now in the net and can be called. Some parameters were filled with default values."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.junction # show junction table"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "All create functions return the pandapipes index of the element that was created, for example the variable junction1 is now equal to the index of the junction with the name \"Connection to External Grid\" (which is 0):\n"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "junction1"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.junction.loc[junction1]"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We use these variables for creating bus and branch elements in the following."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### External Grid"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<img src=\"pics/simple_network-ext_grid.png\">\n",
    "\n",
    "We now create a medium pressure external grid connection that serves as slack node for the pipe flow calculation. The pressure is set to 1.1 bar:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "medium_pressure_grid = pp.create_ext_grid(net, junction=junction1, p_bar=1.1, t_k=293.15, name=\"Grid Connection\")\n",
    "\n",
    "net.ext_grid # show external grid table"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Pipes"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The network includes 5 pipes between two junctions each. The junctions and pipes lengths are defined in the network diagram:\n",
    "\n",
    "<img src=\"pics/simple_network-pipes.png\">\n",
    "\n",
    "For all pipes we want a diameter of 300 mm. "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "pipe1 = pp.create_pipe_from_parameters(net, from_junction=junction1, to_junction=junction2, length_km=10, diameter_m=0.3, name=\"Pipe 1\")\n",
    "pipe2 = pp.create_pipe_from_parameters(net, from_junction=junction2, to_junction=junction3, length_km=2, diameter_m=0.3, name=\"Pipe 2\")\n",
    "pipe3 = pp.create_pipe_from_parameters(net, from_junction=junction2, to_junction=junction4, length_km=2.5, diameter_m=0.3, name=\"Pipe 3\")\n",
    "pipe4 = pp.create_pipe_from_parameters(net, from_junction=junction3, to_junction=junction5, length_km=1, diameter_m=0.3, name=\"Pipe 4\")\n",
    "pipe5 = pp.create_pipe_from_parameters(net, from_junction=junction4, to_junction=junction6, length_km=1, diameter_m=0.3, name=\"Pipe 5\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The full pipe table looks like this:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.pipe # show pipe table"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The parameters from_junction and to_junction define the orientation of the pipe. If the fluid streams in fact from the from_junction to to_junction, the resulting fluid velocity is positive. If the fluid stream direction is opposite, the resulting velocity is negative."
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Valve"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "There is one valve between Junction 5 and Juncion 6. It is open so that the gas can circulate.\n",
    "\n",
    "<img src=\"pics/simple_network-valve.png\">"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "valve = pp.create_valve(net, from_junction=junction5, to_junction=junction6, diameter_m=0.3, opened=True)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "As we see in the valve table below the default value for the loss_coefficient of the valve is zero. Also, all valves have a length of 0 meter, because we consider ideal valves. However, if needed you can change the loss_coefficient parameter. "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.valve # show valve table"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Sink\n",
    "\n",
    "<img src=\"pics/simple_network-sink.png\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The sink element is used to model by default a constant consumption. We create here a gas consumption sink with a mass flow of 545 gramm per second. Sinks and sources always have to be assigned to a particular junction. The sign of the mass flow is positive."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "sink = pp.create_sink(net, junction=junction4, mdot_kg_per_s=0.545, name=\"Sink 1\")\n",
    "net.sink"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### Source\n",
    "\n",
    "<img src=\"pics/simple_network-source.png\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The source element is used to model a generation of heat or gas. It could be for example a biogas plant that is directly connected to the gas network or a combined heat and power plant.\n",
    "In this example, we assume that a biogas plant is directly feeding into the gas grid with a constant value of 234 gramm per second. The sign of the mass flow is also positive."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "source = pp.create_source(net, junction=junction3, mdot_kg_per_s=0.234, name=\"Source 1\")"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.source"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "We are done. Now, the net includes all the elements from the picture."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Finally, the gas flow can be calculated with the `pipeflow` command:"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "pp.pipeflow(net)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "The results are written to `res_...` tables. They were added to the `net`container. "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net # result tables have been added to the net "
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.res_junction # calculated pressure and temperature at junctions"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [],
   "source": [
    "net.res_pipe  # velocities, mass flows through pipes and other results\n",
    "\n"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.7.3"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
